package tengxun

import (
	"context"
	"time"

	"gitee.com/hexug/devcloud/cmdb/apps/resource"
	"gitee.com/hexug/devcloud/cmdb/common/logger"
	"github.com/alibabacloud-go/tea/tea"
	"github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/common"
	cvm "github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/cvm/v20170312"
)

func (t *TencentClient) SyncHost(ctx context.Context) error {
	client, err := t.NewCvmClient()
	if err != nil {
		logger.L().Errorw(err.Error())
		return err
	}
	request := cvm.NewDescribeInstancesRequest()

	// request.Offset = common.Int64Ptr((t.PageNumber - 1) * t.PageSize)
	request.Limit = common.Int64Ptr(t.PageSize)
PAGE_QUERY:
	// 返回的resp是一个DescribeInstancesResponse的实例，与请求对象对应
	response, err := client.DescribeInstances(request)
	if err != nil {
		logger.L().Errorf("同步失败：%s", err.Error())
		return err
	}
	for _, instance := range response.Response.InstanceSet {
		if instance != nil {
			r := t.InstanceToResource(instance)
			t.hook(ctx, r)
		}
	}
	if tea.Int64Value(response.Response.TotalCount)-(tea.Int64Value(request.Offset)+t.PageSize) > 0 {
		request.Offset = common.Int64Ptr(tea.Int64Value(request.Offset) + t.PageSize)
		//等待获取一个可用的令牌
		t.tb.Wait(1)
		goto PAGE_QUERY
	}
	return nil
}

func (t *TencentClient) InstanceToResource(item *cvm.Instance) *resource.Resource {
	r := resource.NewResource()
	meta := resource.NewMeta()
	r.Meta = meta
	spec := resource.NewSpec()
	r.Spec = spec
	cost := resource.NewCost()
	r.Cost = cost
	status := resource.NewStatus()
	r.Status = status

	//TODO 因为没有domain 所以这里手动设置
	meta.Domain = "default"
	meta.Namespace = "default"
	meta.Id = tea.StringValue(item.InstanceId)
	result, err := time.ParseInLocation("2006-01-02T15:04:05Z", tea.StringValue(item.CreatedTime), time.UTC)
	//如果错误则退出
	if err != nil {
		logger.L().Errorf("时间转换失败：%s", err.Error())
		meta.CreateAt = time.Now().Unix()
	} else {
		meta.CreateAt = result.Unix()
	}
	meta.SyncAt = time.Now().Unix()

	spec.Cpu = int32(tea.Int64Value(item.CPU))
	if item.GPUInfo != nil {
		spec.Gpu = int32(tea.Float64Value(item.GPUInfo.GPUCount))
	}
	spec.Memory = int32(tea.Int64Value(item.Memory) * 1024)
	spec.Vendor = resource.VENDOR_TENCENT
	if item.Placement != nil {
		spec.Zone = tea.StringValue(item.Placement.Zone)
	}
	spec.Name = tea.StringValue(item.InstanceId)
	if item.ExpiredTime != nil {
		if result, err := time.ParseInLocation("2006-01-02T15:04:05Z", tea.StringValue(item.ExpiredTime), time.UTC); err != nil {
			logger.L().Errorf("时间转换失败：%s", err.Error())
		} else {
			spec.ExpireAt = result.Unix()
		}
	}

	spec.UpdateAt = time.Now().Unix()
	spec.Owner = tea.StringValue(item.DefaultLoginUser)
	if item.SystemDisk != nil {
		spec.Storage = int32(tea.Int64Value(item.SystemDisk.DiskSize))
	}
	if item.InternetAccessible != nil {
		spec.BandWidth = int32(tea.Int64Value(item.InternetAccessible.InternetMaxBandwidthOut))
	}

	switch tea.StringValue(item.InstanceChargeType) {
	//表示预付费，即包年包月
	case "PREPAID":
		cost.PayMode = resource.PAY_MODE_PRE_PAY
		//表示后付费，即按量计费
	case "POSTPAID_BY_HOUR":
		cost.PayMode = resource.PAY_MODE_POST_PAY
		//表示竞价实例付费
	case "SPOTPAID":
		cost.PayMode = resource.PAY_MODE_SPOT_PAY
	default:
		cost.PayMode = resource.PAY_MODE_NULL
	}

	status.PublicAddress = tea.StringSliceValue(item.PublicIpAddresses)
	status.PrivateAddress = tea.StringSliceValue(item.PrivateIpAddresses)
	status.Phase = tea.StringValue(item.InstanceState)
	switch tea.StringValue(item.RestrictState) {
	case "NORMAL":
		status.LockMode = resource.LOCK_MODE_UNLOCK
	case "EXPIRED":
		status.LockMode = resource.LOCK_MODE_LOCK_BY_EXPIRATION
	case "PROTECTIVELY_ISOLATED":
		status.LockMode = resource.LOCK_MODE_MANUAL_LOCK
	default:
		status.LockMode = resource.LOCK_MODE_MANUAL_LOCK
	}

	//搜集tag
	for _, tag := range item.Tags {
		t := resource.NewKVTag(resource.TAG_PURPOSE_THIRDPARTY, tea.StringValue(tag.Key), tea.StringValue(tag.Value))
		r.AddTag(t)
	}
	return r
}
